package com.lsc.jiujia.service.serviceImpl;

import com.alibaba.fastjson.JSONArray;
import com.alibaba.fastjson.JSONObject;
import com.lsc.jiujia.entity.IPEntity;
import com.lsc.jiujia.entity.ParamEntity;
import com.lsc.jiujia.entity.UserInfoEntity;
import com.lsc.jiujia.mapper.IpMapper;
import com.lsc.jiujia.service.PlayService;
import com.lsc.jiujia.util.IPUtil;
import com.lsc.jiujia.util.PlayUtil;
import lombok.extern.slf4j.Slf4j;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.http.HttpEntity;
import org.springframework.http.HttpHeaders;
import org.springframework.http.HttpMethod;
import org.springframework.scheduling.annotation.Scheduled;
import org.springframework.stereotype.Service;
import org.springframework.web.client.RestTemplate;

import java.text.SimpleDateFormat;
import java.util.*;
import java.util.concurrent.ArrayBlockingQueue;
import java.util.concurrent.ThreadPoolExecutor;
import java.util.concurrent.TimeUnit;

@Slf4j
@Service
public class PlayServiceImpl implements PlayService {

    private String baseUrl = "https://cloud.cn2030.com/sc/wx/HandlerSubscribe.ashx";

    private String getCustSubscribeDateDetailUrl = "?act=GetCustSubscribeDateDetail&id=%s&pid=%s&scdate=%s";

    private String getCaptcha = "?act=getCaptcha";

    private String getCaptchaVerify = "?act=CaptchaVerify&token=''&x=''&y=''";

    private String save20Url = "?act=Save20";

    private String getUserInfoUrl = "?act=User";

    private String pid;
    @Autowired
    private PlayUtil playUtil;
    @Autowired
    private IPUtil ipUtil;

    @Autowired
    private IpMapper ipMapper;

    @Override
    public String play(ParamEntity param) {

        ThreadPoolExecutor threadPoolExecutor = new ThreadPoolExecutor(100,100,0,
                TimeUnit.SECONDS,new ArrayBlockingQueue<>(100));
        //获取代理IP
        List<IPEntity> IpList = ipMapper.findAll();
        for(int i=0;i<IpList.size();i++){
            IPEntity ipEntity = IpList.get(i);
            Integer port = Integer.valueOf(ipEntity.getIPPort());
            threadPoolExecutor.submit(() ->{
                playProcess(ipEntity.getIPAddress(),port,param);
            });
        }

        return null;
    }

    @Override
    public String testSql(){
        log.info("开始组装实体");
        IPEntity ipEntity = new IPEntity();
        ipEntity.setId(1L);
        ipEntity.setIPAddress("127.0.0.1");
        ipEntity.setIPPort("8080");
        ipEntity.setIPType("自己");
        ipEntity.setIPSpeed("2秒");
        ipMapper.save(ipEntity);
        log.info("jpa保存实体成功！");
        return "success";
    }

    /**
     * 定时器爬取IP地址，并且保存在数据库里
     */
    @Scheduled(cron = "0 0 12 * * ?")
    private void saveIP(){
        IPUtil.getIPList();
    }


    private void playProcess(String ip,Integer port,ParamEntity param){
        //获取预约时间
        JSONObject subscribeDateDetailJson = getCustSubscribeDateDetail(ip,port,param);
        String status = subscribeDateDetailJson.getString("status");
        JSONArray list = subscribeDateDetailJson.getJSONArray("list");
        String mxid = list.getJSONObject(0).getString("mxid");
        if("200".equals(status)){
            //获取验证码
            JSONObject captcha = getCaptcha(ip,port,param);
            //验证验证码
            JSONObject yanzhengJson =yanZheng(ip,port,param);

            if("200".equals(yanzhengJson.getString("status"))){
                UserInfoEntity userInfo = getUserInfo(ip,port,param);
                userInfo.setMxid(mxid);

                userInfo.setGuid(yanzhengJson.getString("guid"));
                userInfo.setPid(param.getPid());
                Date now =new Date();
                SimpleDateFormat sdf = new SimpleDateFormat("YYYY-MM-DD");
                userInfo.setDate(sdf.format(now));
                //如果验证通过，立马提交预约
                JSONObject result = save(ip,port,param,userInfo);
                if("200".equals(result.getString("status"))){
                    log.info( "成功抢到九价疫苗！！！！");
                }
            }
        }
    }

    private HttpHeaders assembleHeader(ParamEntity param){
        HttpHeaders headers = new HttpHeaders();
        headers.set("User-Agent","Mozilla/5.0 (Windows NT 6.1; WOW64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/53.0.2785.143 Safari/537.36 MicroMessenger/7.0.9.501 NetType/WIFI MiniProgramEnv/Windows WindowsWechat");
        headers.set("Host","cloud.cn2030.com");
        headers.set("Cookie",param.getCookie());
        headers.set("zftsl",param.getZftsl());
        headers.set("Referer",param.getReferer());
        return headers;
    }


    /**
     * 根据医院获取预约时间
     */

    private JSONObject getCustSubscribeDateDetail(String ip,Integer port,ParamEntity param){
        String url = baseUrl+getCustSubscribeDateDetailUrl;
        Date now =new Date();
        SimpleDateFormat sdf = new SimpleDateFormat("YYYY-MM-DD");
        url = String.format(url,param.getId(),"1",sdf.format(now));
        Map<String,String> params = new HashMap<>();
        HttpHeaders headers = assembleHeader(param);
        JSONObject result =playUtil.sendRestfulReq(ip,port,url, HttpMethod.GET,new HttpEntity<>(params, headers),String.class);
        log.info(JSONObject.toJSONString(result));
        return result;
    }

    /**
     * 获取预约详细信息
     */

    /**
     * 获取验证码
     */
    private JSONObject getCaptcha(String ip,Integer port,ParamEntity param){
        String url = baseUrl+getCaptcha;

        Map<String,String> params = new HashMap<>();
        HttpHeaders headers = assembleHeader(param);
        JSONObject result =playUtil.sendRestfulReq(ip,port,url, HttpMethod.GET,new HttpEntity<>(params, headers),String.class);
        log.info(JSONObject.toJSONString(result));
        return result;
    }
    /**
     * 验证验证码
     */
    private JSONObject yanZheng(String ip,Integer port,ParamEntity param){
        String url = baseUrl+getCaptchaVerify;

        Map<String,String> params = new HashMap<>();
        HttpHeaders headers = assembleHeader(param);
        JSONObject result =playUtil.sendRestfulReq(ip,port,url, HttpMethod.GET,new HttpEntity<>(params, headers),String.class);
        log.info(JSONObject.toJSONString(result));
        return result;
    }
    /**
     * 提交数据保存
     */
    private JSONObject save(String ip,Integer port,ParamEntity param,UserInfoEntity userInfo){
        String url = baseUrl+save20Url+"&"+userInfo.getUserInfo();

        Map<String,String> params = new HashMap<>();
        HttpHeaders headers = assembleHeader(param);
        JSONObject result =playUtil.sendRestfulReq(ip,port,url, HttpMethod.GET,new HttpEntity<>(params, headers),String.class);
        log.info(JSONObject.toJSONString(result));
        return result;
    }

    /**
     * 根据cookie获取用户信息
     */
    private UserInfoEntity getUserInfo(String ip,Integer port,ParamEntity param){
        String url = baseUrl+getUserInfoUrl;

        Map<String,String> params = new HashMap<>();
        HttpHeaders headers = assembleHeader(param);
        JSONObject result =playUtil.sendRestfulReq(ip,port,url, HttpMethod.GET,new HttpEntity<>(params, headers),String.class);
        if(result!= null&&"200".equals(result.getString("status"))){
            JSONObject user = result.getJSONObject("user");
            UserInfoEntity userInfoEntity = new UserInfoEntity();
            userInfoEntity.setBirthday(user.getString("birthday"));
            userInfoEntity.setCname(user.getString("cname"));
            userInfoEntity.setIdcard(user.getString("idcard"));
            userInfoEntity.setDoctype(user.getString("doctype"));
            userInfoEntity.setTel(user.getString("tel"));
            return userInfoEntity;
        }
        return null;
    }
}
